package com.whfc.emp.xxl.job;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.whfc.XxlJobConfig;
import com.whfc.common.constant.QueueConst;
import com.whfc.common.enums.DeviceType;
import com.whfc.emp.dao.AppBroadcastRecordEmpMapper;
import com.whfc.emp.dao.AppBroadcastRecordMapper;
import com.whfc.emp.dto.AppBroadcastRecordEmpDTO;
import com.whfc.emp.entity.AppBroadcastRecord;
import com.whfc.emp.entity.AppBroadcastRecordEmp;
import com.whfc.emp.enums.AppBroadcastSendState;
import com.whfc.emp.helmet.ZbznApi;
import com.whfc.hdc.dto.AppDeviceDTO;
import com.whfc.hdc.service.AppDeviceService;
import com.xxl.job.core.context.XxlJobHelper;
import com.xxl.job.core.handler.annotation.XxlJob;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.amqp.core.AmqpTemplate;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.stereotype.Component;

import java.util.Date;
import java.util.List;

/**
 * 广播重试
 *
 * @author : qzexing
 * @version : 1.0
 * @date : 2020/7/6 11:44
 */
@Component
@ConditionalOnBean(XxlJobConfig.class)
public class AppBroadcastRetryJob {

    @Autowired
    private AppBroadcastRecordMapper appBroadcastRecordMapper;

    @Autowired
    private AppBroadcastRecordEmpMapper appBroadcastRecordEmpMapper;

    @DubboReference(interfaceClass = AppDeviceService.class, version = "1.0.0")
    private AppDeviceService commonDeviceService;

    @Autowired
    private AmqpTemplate amqpTemplate;

    /**
     * 重试次数
     */
    private static Integer retryCount = 3;

    /**
     * 重试间隔时间 单位: 毫秒
     */
    private static Long intervalSeconds = 180000L;

    /**
     * 广播过期时间  单位：毫秒
     */
    private static Long expiredSeconds = 600000L;

    /**
     * 每分钟检查消息状态
     */
    @XxlJob("broadcastRetry")
    public void broadcastRetry() {
        List<AppBroadcastRecordEmpDTO> list = appBroadcastRecordEmpMapper.selectUndoneRecordEmpList();
        Date now = new Date();
        for (AppBroadcastRecordEmpDTO recordEmpDTO : list) {
            long sendTime = recordEmpDTO.getSendTime().getTime();
            if (sendTime + expiredSeconds < now.getTime()) {
                //消息过期
                recordEmpDTO.setState(AppBroadcastSendState.EXPIRED.getValue());
            } else {
                if (recordEmpDTO.getRetryCnt() >= retryCount) {
                    //超过了重试次数
                    recordEmpDTO.setState(AppBroadcastSendState.EXPIRED.getValue());
                } else {
                    //当前重试次数
                    int retryCnt = recordEmpDTO.getRetryCnt() + 1;
                    //重试时间
                    long retryTime = retryCnt * intervalSeconds;
                    if (sendTime + retryTime < now.getTime()) {
                        //重试
                        //获取消息类型
                        AppBroadcastRecord record = appBroadcastRecordMapper.selectByPrimaryKey(recordEmpDTO.getRecordId());
                        recordEmpDTO.setContent(record.getContent());
                        recordEmpDTO.setVoiceType(recordEmpDTO.getVoiceType());
                        //发送广播
                        sendBroadcast(recordEmpDTO);
                        recordEmpDTO.setRetryCnt(retryCnt);
                        recordEmpDTO.setState(AppBroadcastSendState.SEND.getValue());
                    }
                }
            }
            AppBroadcastRecordEmp recordEmp = new AppBroadcastRecordEmp();
            BeanUtils.copyProperties(recordEmpDTO, recordEmp);
            appBroadcastRecordEmpMapper.updateByPrimaryKeySelective(recordEmp);
        }
    }

    /**
     * 发送广播
     *
     * @param recordEmpDTO 广播DTO
     */
    private void sendBroadcast(AppBroadcastRecordEmpDTO recordEmpDTO) {
        AppDeviceDTO appDeviceDTO = commonDeviceService.getDeviceById(recordEmpDTO.getDeviceId());
        if (appDeviceDTO == null) {
            return;
        }

        // 如果是筑邦智能定位安全帽
        if ("zbzn".equals(appDeviceDTO.getExt1())&&appDeviceDTO.getType()== DeviceType.helmet.getValue()) {
            JSONObject jsonData = new JSONObject();
            if (StringUtils.isNotBlank(recordEmpDTO.getContent())) { // 自定义 语音播报
                jsonData = ZbznApi.sendTextToAudio(appDeviceDTO.getSn(), 1,recordEmpDTO.getContent());
            }else {    // 固定播报
                jsonData = ZbznApi.sendVoice(appDeviceDTO.getSn(), recordEmpDTO.getVoiceType());
            }
            if (200 != jsonData.getInteger("code")) {
                //修改广播为未发送状态
                appBroadcastRecordEmpMapper.updateState(recordEmpDTO.getId(), AppBroadcastSendState.UNSENT.getValue());
            }
            return;
        }

        recordEmpDTO.setCode(appDeviceDTO.getCode());
        //获取设备Code
        try {
            amqpTemplate.convertAndSend(QueueConst.EMP_HELMET_BOARDCAST, JSON.toJSONString(recordEmpDTO));
        } catch (Exception e) {
            XxlJobHelper.handleFail("发送广播失败" + e.getMessage());
            //修改广播为未发送状态
            appBroadcastRecordEmpMapper.updateState(recordEmpDTO.getId(), AppBroadcastSendState.UNSENT.getValue());
        }
    }
}
